<?php
class mysql{
	private $db=array();
	private $queryID=null;
	private $resources=array();
	private $query='';
    public function init($params=array()){
    	$this->db=$params['db'];
    	if(isset($this->db[0])){
	    	$this->resources['master']=$this->db[0];
	    	if($this->db['SEPARATE']){
	    		$dbnum=count($this->db)-2;
	    		if($dbnum<1){$this->yum->error('SEPARATE config is error!');}
	    		$this->resources['slave']=$this->db[rand(1,$dbnum)];
	    	}
    	}else{
    		$this->yum->error('mysql config is error!');
    	}
    }
     public function connect($params){
     	if(is_string($params)){
     		$params=&$this->resources[$params];
     	}elseif(is_array($params)){
     		$this->resources[$params['key']]=array_diff_key($params,array('key'=>''));
     		$params=&$this->resources[$params['key']];
     	}
     	$params['ID']=($params['pconnect'])?
		mysql_pconnect($params['host'].':'.$params['port'],$params['user'],$params['password']):
		mysql_connect($params['host'].':'.$params['port'],$params['user'],$params['password']);
		if(is_resource($params['ID'])){
			if(!mysql_select_db($params['name'],$params['ID'])){
				$this->Msgerror($params['ID']);
			}
			mysql_query('SET NAMES \''.$params['charset'].'\'',$params['ID']);
		}else{
			$this->Msgerror($params['ID']);
		}
     }
    private function parse($target=null){
    	$parse=array('RES'=>$target,'ACT'=>0);
		switch(strtoupper(substr($this->query,0,strpos($this->query,' ')))){
			case 'SELECT':$parse['ACT']=0;break;
			case 'INSERT':$parse['ACT']=1;break;
			case 'UPDATE':$parse['ACT']=2;break;
			case 'DELETE':$parse['ACT']=3;break;
			case 'REPLACE':$parse['ACT']=4;break;
			default :$parse['ACT']=5;break;
		}
    	if($parse['RES']===null){
			if($this->db['SEPARATE']){
				$parse['RES']=($parse['ACT']==0)?'slave':'master';
			}else{
				$parse['RES']='master';
			}
    	}else{
    		if(empty($this->resources[$parse['RES']])){
    			$this->yum->error('database not found!');
    		}
    	}
    	if(!is_resource($this->resources[$parse['RES']]['ID'])){
    		$this->connect($parse['RES']);
		}
		return $parse;
    }
    public function query($query,$mode=1,$res=null){
    	$this->query=trim($query);$action=$this->parse($res);
		$this->queryID=mysql_query($this->query,$this->resources[$action['RES']]['ID']);
		if($this->queryID===false){$this->Msgerror($this->resources[$action['RES']]['ID']);return false;}
		if($action['ACT']==0){
			switch($mode){
				case 1:$mode=MYSQL_ASSOC;break;
				case 2:$mode=MYSQL_BOTH;break;
				default :$mode=MYSQL_NUM;;break;
			}
			return $this->_list($mode);
		}elseif($action['ACT']==1){
			if($mode==1){
				return $this->insert_id($action['RES']);
			}else{
				return $this->affected_rows($action['RES']);
			}
		}elseif($action['ACT']>=2&&$action['ACT']<=4){
			return $this->affected_rows($action['RES']);
		}
    }
    public function last_query(){
    	return $this->query;
    }
    private function _list($mode){
		$result=array();
		$field=mysql_field_flags($this->queryID,0);
		if(strripos($field,'AUTO_INCREMENT')!==false||strripos($field,'UNIQUE_KEY')!==false){
			$key=($mode===1)?mysql_field_name($this->queryID,0):0;
			while($row=mysql_fetch_array($this->queryID,$mode)){$result[$row[$key]]=$row;}
		}else{
			while($row=mysql_fetch_array($this->queryID,$mode)){$result[]=$row;}
		}
		return $result;
    }
    private function affected_rows($res){
     	return mysql_affected_rows($this->resources[$res]['ID']);
    }
    private function insert_id($res){
    	return mysql_insert_id($this->resources[$res]['ID']);
    }
    public function startTrans($target='master'){
    	$this->query('SET AUTOCOMMIT=0',0,$target);
    	$this->query('START TRANSACTION',0,$target);
		return ;
    }
    public function commit($target='master'){
    	$this->query('COMMIT',0,$target);
    	$this->query('SET AUTOCOMMIT=1',0,$target);
		return ;
    }
    public function rollback($target='master'){
    	$this->query('ROLLBACK',0,$target);
    	$this->query('SET AUTOCOMMIT=1',0,$target);
		return ;
    }
    public function free(){
        @mysql_free_result($this->queryID);
        $this->queryID=0;
    }
    public function close($Res=null){
    	if(is_string($Res)){
    		@mysql_close($this->resources[$Res]['ID']);
    	}else{
    		foreach($this->resources as $key=>$value){
	    		if(is_resource($value['ID'])){
	    			@mysql_close($value['ID']);
	    		}
    		}
    	}
    }
    public function select($table,$params=array(),$mode=1,$res=null){
    	$select='*';$where='';$group='';$order='';$limit='';
    	if(!empty($params['select'])){
    		$select='';
    		if(is_string($params['select'])){
				$select=$params['select'];
    		}else if(is_array($params['select'])){
	     		foreach($params['select'] as $key => $value){
					$select.="`$value`,";
				}
				$select=substr_replace($select,'',-1,1);
    		}
    	}
    	if(!empty($params['group'])){
    		$group.=' GROUP BY ';
    		if(is_string($params['group'])){
				$group.=$params['group'];
    		}else if(is_array($params['group'])){
	    		foreach($params['group'] as $value){
	    			$group.="`$value`,";
	    		}
	    		$group=substr_replace($group,'',-1,1);
    		}
		}
		if(!empty($params['order'])){
			$order.=' ORDER BY ';
			foreach($params['order'] as $key => $value){
				$order.=$key.' '.$value.',';
    		}
    		$order=substr_replace($order,'',-1,1);
		}
		if(!empty($params['limit'])){
			$limit.=' LIMIT ';
			$limit.=count($params['limit'])==1?$params['limit']:$params['limit'][0].','.$params['limit'][1];
		}
		return $this->query('SELECT '.$select.' FROM '.$table.$this->where($params['where']).$group.$order.$limit.';',$mode,$res);
    }
    public function update($table,$params){
    	$set='';
		if(!empty($params['set'])){
			if(is_string($params['set'])){
				$set=$params['set'];
			}else if(is_array($params['set'])){
				foreach($params['set'] as $key => $value){
					$set.=$key;
					$set.=is_string($value)?"'$value'":$value;
					$set.=',';
				}
				$set=substr_replace($set,'',-1,1);
			}
		}else{
			$this->yum->error('update params is error。');
		}
		return $this->query('UPDATE `'.$table.'` SET '.$set.$this->where($params['where']).';');
    }
    public function delete($table,$params){
    	$order='';$limit='';
		if(isset($params['order'])&&!empty($params['order'])){
			$order.=' ORDER BY ';
			foreach($params['order'] as $key => $value){
				$order.='`'.$key.'` '.$value.',';
    		}
    		$order=substr_replace($order,'',-1,1);
		}
		if(isset($params['limit'])&&!empty($params['limit'])){
			$limit.=' LIMIT ';
			$limit.=count($params['limit'])==1?$params['limit']:$params['limit'][0].','.$params['limit'][1];
		}
		return $this->query('DELETE FROM `'.$table.'`'.$this->where($params['where']).$order.$limit.';');
    }
    public function insert($table,$params,$mode=0,$res=null){
		return $this->query($this->write('INSERT',$table,$params),$mode,$res);
    }
    public function replace($table,$params,$mode=0,$res=null){
		return $this->query($this->write('REPLACE',$table,$params),$mode,$res);
    }
    private function where($where,$type='AND'){
    	$result='';
    	if(is_string($where)){
			$result.=$where;
    	}else if(is_array($where)){
			foreach($where as $key=>$value){
				$result.=$key;
				if(is_string($value)){
					$result.="'$value'";
				}elseif(is_numeric($value)){
					$result.=$value;
				}elseif(is_array($value)){
						$result.='(';
					foreach($value as $v){
						$result.=is_string($v)?"'$v'":$v;
						$result.=',';
					}
					$result=substr_replace($result,'',-1,1);
					$result.=')';
				}
				$result.=' '.$type.' ';
			}
			$result=substr_replace($result,'',-5,5);
    	}
    	return $result==''?'':(' WHERE '.$result);
    }
    private function write($action,$table,$params){
		$field='';$values='';
		if(empty($params['field'])||empty($params['value'])){
			$values.='(';
			foreach($params as $key => $value){
				$field.="`$key`,";
				$values.=(is_string($value)?"'$value'":$value).',';
			}
			$values=substr_replace($values,'',-1,1);
			$values.='),';
		}else{
			foreach($params['field'] as $value){
				$field.="`$value`,";
			}
			foreach($params['value'] as $value){
				$values.='(';
				foreach($value as $v){
					$values.=(is_string($v)?"'$v'":$v).',';
				}
				$values=substr_replace($values,'',-1,1);
				$values.='),';
			}
		}
		$field=substr_replace($field,'',-1,1);
		$values=substr_replace($values,'',-1,1);
		return	$action.' INTO `'.$table.'`('.$field.') VALUES'.$values.';';
    }
	public function Msgerror($resource){
		echo '<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />';
		echo "<fieldset>";
		echo "<legend>错误信息提示:</legend><br />";
		echo "<div style='font-size:14px; clear:both; font-family:Verdana, Arial, Helvetica, sans-serif;'>";
		echo "<div style='height:20px; background:#000000; border:1px #000000 solid'>";
		echo "<font color='white'>错误号：".mysql_errno($resource)."</font>";
		echo "</div><br />";
		echo "错误原因：<br /><br />";
		echo "<div style='height:20px; background:#FF0000; border:1px #FF0000 solid'>";
		echo "<font color='white'>".mysql_error($resource)."</font>";
		echo "</div>";
		echo "<font color='red'><pre>".$this->query."</pre></font>";
		echo "<br />";
		echo "</div>";
		echo "</fieldset>";
		echo "<br />";
		$this->close();
	}
    public function __destruct(){
        $this->close();
    }
}
?>